package com.yeziji.devops.sql.info;

import com.yeziji.devops.constant.SqlExecuteTypeEnum;
import com.yeziji.devops.sql.base.SqlConstructorBase;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;

import java.util.List;
import java.util.Map;

/**
 * 记录日志 dto
 *
 * @author gzkemays
 * @since 2023/01/16 1:09 PM
 */
@Data
@NoArgsConstructor
@AllArgsConstructor
public class SqlRecordInfo {
    /**
     * 记录 SQL
     */
    private String sql;

    /**
     * 拟定操作用户 id
     */
    private long userId;

    /**
     * SQL 结果集
     */
    private Object result;

    /**
     * 数据源名称
     */
    private String sourceName;

    /**
     * 操作类型
     */
    private SqlExecuteTypeEnum type;

    /**
     * SQL 构造器
     */
    private SqlConstructorBase sqlConstructor;

    /**
     * 原结果集
     * <p>一般作用于记录回滚</p>
     */
    private List<Map<String, Object>> originalResult;

    /**
     * 自定义 builder
     *
     * @return {@link RecordLogBuilder}
     */
    public static RecordLogBuilder builder() {
        return new RecordLogBuilder();
    }

    /**
     * 构建者模式
     */
    public static final class RecordLogBuilder {
        private String sql;
        private long userId;
        private Object result;
        private String sourceName;
        private SqlExecuteTypeEnum type;
        private SqlConstructorBase sqlConstructor;
        private List<Map<String, Object>> originalResult;

        private RecordLogBuilder() {
        }

        public RecordLogBuilder userId(long userId) {
            this.userId = userId;
            return this;
        }

        public RecordLogBuilder type(SqlExecuteTypeEnum type) {
            this.type = type;
            return this;
        }

        public RecordLogBuilder originalResult(List<Map<String, Object>> originalResult) {
            this.originalResult = originalResult;
            return this;
        }

        public RecordLogBuilder sql(String sql) {
            this.sql = sql;
            return this;
        }

        public RecordLogBuilder sourceName(String sourceName) {
            this.sourceName = sourceName;
            return this;
        }

        public RecordLogBuilder result(Object result) {
            this.result = result;
            return this;
        }

        public RecordLogBuilder sqlConstructor(SqlConstructorBase sqlConstructor) {
            this.sqlConstructor = sqlConstructor;
            return this;
        }

        public SqlRecordInfo build() {
            SqlRecordInfo sqlRecordInfo = new SqlRecordInfo();
            sqlRecordInfo.setSql(this.sql);
            sqlRecordInfo.setUserId(this.userId);
            sqlRecordInfo.setResult(this.result);
            sqlRecordInfo.setSourceName(this.sourceName);
            sqlRecordInfo.setSqlConstructor(this.sqlConstructor);
            sqlRecordInfo.setOriginalResult(this.originalResult);
            if (this.type == null) {
                sqlRecordInfo.setType(SqlExecuteTypeEnum.getByValue(sqlConstructor.getType()));
            } else {
                sqlRecordInfo.setType(this.type);
            }
            return sqlRecordInfo;
        }
    }
}
